package com.tanhua.api.mongo;

import cn.hutool.core.collection.CollectionUtil;
import com.tanhua.mongo.*;
import com.tanhua.vo.PageBeanVo;
import com.tanhua.vo.UserHolder;
import org.apache.dubbo.config.annotation.Service;
import org.bson.types.ObjectId;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Sort;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Field;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.data.mongodb.core.query.Update;

import java.util.ArrayList;
import java.util.Calendar;
import java.util.List;

@Service
public class PublishApiImpl implements PublishApi {

    @Autowired
    private MongoTemplate mongoTemplate;
    @Autowired
    private IdService idService;

    @Override
    public String save(Publish publish) {
        // 1. 保存数据到动态发布表中
        publish.setCreated(System.currentTimeMillis());
        //pid给大数据使用的 要求：该字段是数值类型的唯一值
        publish.setPid(idService.getNextId("quanzi_publish"));
        mongoTemplate.insert(publish);

        //2.保存数据到个人动态表里面
        Album album = new Album();
        album.setPublishId(publish.getId());
        album.setCreated(publish.getCreated());
        mongoTemplate.insert(album, "quanzi_album_" + publish.getUserId());
        //3.保存动态到好友的时间线表里
        //查询好友
        Query query = new Query(Criteria.where("userID").is(publish.getUserId()));
        List<Friend> friendList = mongoTemplate.find(query, Friend.class);
        if (friendList.size() != 0) {
            for (Friend friend : friendList) {
                Long friendId = friend.getFriendId();
                //插入到好友时间线中
                TimeLine timeLine = new TimeLine();
                timeLine.setCreated(publish.getCreated());
                timeLine.setUserId(publish.getUserId());
                timeLine.setPublishId(publish.getId());
                mongoTemplate.insert(timeLine, "quanzi_time_line_" + friendId);

            }
        }
        return publish.getId().toString();
    }

    @Override
    public PageBeanVo findAlbumByPage(Integer pageNum, Integer pageSize, Long userId) {
        Query query = new Query();
        query.with(new Sort(Sort.Direction.DESC, "created"));
        query.skip((pageNum - 1) * pageSize).limit(pageSize);
        long count = mongoTemplate.count(query, "quanzi_album_" + userId); //总条数
        List<Album> albumList = mongoTemplate.find(query, Album.class, "quanzi_album_" + userId);

        //用于存放审核通过的动态
        List<Publish> publishList = new ArrayList<>();

        if (albumList.size() != 0) {
            for (Album album : albumList) {
                ObjectId publishId = album.getPublishId();
                Publish publish = mongoTemplate.findById(album.getPublishId(), Publish.class);
                if (publish.getState() == 1) {
                    publishList.add(publish);
                }
            }
        }
        PageBeanVo pageBeanVo = new PageBeanVo();
        pageBeanVo.setCounts((long) publishList.size());
        pageBeanVo.setPagesize(pageSize);
        pageBeanVo.setItems(publishList);
        return pageBeanVo;
    }

    @Override
    public PageBeanVo findTimeLineByPage(Integer pageNum, Integer pageSize, Long userId) {

        // 1、查询时间线表

        Query query = new Query();
        query.with(Sort.by(Sort.Order.desc("created")));
        query.skip((pageNum - 1) * pageSize).limit(pageSize);
        List<TimeLine> timeLineList = mongoTemplate.find(query, TimeLine.class, "quanzi_time_line_" + userId);

        // 2、遍历时间线封装动态详情
        List<Publish> publishList = new ArrayList<>();
        if (CollectionUtil.isNotEmpty(timeLineList)) {
            for (TimeLine timeLine : timeLineList) {
                Publish publish = mongoTemplate.findById(timeLine.getPublishId(), Publish.class);
                if (publish.getState() == 1) {
                    publishList.add(publish);
                }
            }
        }

        return new PageBeanVo(pageNum, pageSize, (long) publishList.size(), publishList);
    }


    @Override
    public PageBeanVo findRecommendByPage(Integer pageNum, Integer pageSize, Long userId) {
        Query query = new Query(Criteria.where("userId").is(userId));
        query.with(new Sort(Sort.Direction.DESC, "created"));
        query.skip((pageNum - 1) * pageSize).limit(pageSize);
        List<RecommendQuanzi> recommendQuanziList = mongoTemplate.find(query, RecommendQuanzi.class);
        List<Publish> publishList = new ArrayList<>();
        if (CollectionUtil.isNotEmpty(recommendQuanziList)) {
            for (RecommendQuanzi recommendQuanzi : recommendQuanziList) {
                Publish publish = mongoTemplate.findById(recommendQuanzi.getPublishId(), Publish.class);
                if (publish.getState() == 1) {
                    publishList.add(publish);
                }

            }

        }
        return new PageBeanVo(pageNum, pageSize, (long) publishList.size(), publishList);
    }

    @Override
    public Publish findPublishById(String publishId) {
        Publish publish = mongoTemplate.findById(new ObjectId(publishId), Publish.class);
        return publish;
    }

    @Override
    public PageBeanVo findMessages(Integer pageNum, Integer pageSize, Long userId, Integer state) {
        Query query = new Query();
        Criteria criteria = new Criteria();
        if (userId != null) {
            criteria.and("userId").is(userId);
        }
        if (state != null) {
            criteria.and("state").is(state);
        }
        query.addCriteria(criteria);
        List<Publish> publishList = mongoTemplate.find(query, Publish.class);
        long count = mongoTemplate.count(query, Publish.class);
        mongoTemplate.count(query, Publish.class);
        PageBeanVo pageBeanVo = new PageBeanVo(pageNum, pageSize, count, publishList);
        return pageBeanVo;
    }

    @Override
    public void updateState(String publishId, int state) {
        Query query = new Query(Criteria.where("id").is(publishId));
        Update update = new Update();
        update.set("state", state);
        mongoTemplate.upsert(query, update, Publish.class);
    }
    @Override
    public Publish findByPid(String pid) {
        long id = Long.parseLong(pid);
        Query query = new Query(Criteria.where("pid").is(id));
        Publish publish = mongoTemplate.findOne(query, Publish.class);
        return publish;
    }
}